#include "includes.h"
#include "txd_qq_link.h"


int TestQQLinkFlag = 0;

#define QQLINK_RSSI_MIN			-70
#define QQLINK_LOCK_CH_TIMEOUT	50  // 50 ticks
#define QQLINK_PROVISION_TIMEOUT    600  // 600 ticks
extern OS_EVENT * pLinkUpSem;

void txd_qq_link_complete(txd_qq_link_result_t *result)
{
    if(!result) {
        return;
    }

    InfWiFiStop();
    TestQQLinkFlag = TEST_FLAG_QQLINK_DONE;

    printf("\n#########ip:%s",result->ip);
    printf("\n#########port:%d",result->port);
    printf("\n#########ssid:%s",result->ssid);
    printf("\n#########psword:%s",result->password);

    InfSsidSet(result->ssid, strlen(result->ssid));
    InfKeySet(0, result->password, strlen(result->password));
    DRV_WiFi_StationCustomModeStart((char *)SysParam.WiFiCfg.Ssid,(char *)SysParam.WiFiCfg.PSK);

    return;
}

void txd_set_qq_link_channel(int32_t nchannel)
{
    printf("txd_set_qq_link_channel nchannel\n");

    TestQQLinkFlag = TEST_FLAG_SWITCH_CHANNEL;
}

VOID TestQQLinkRecvCb(UINT8 *pRecvBuf, UINT32 pRecvLen)
{
    UINT32 Ret = 0;
    
    Ret = txd_fill_80211_frame(pRecvBuf, pRecvLen, 0);
    if (Ret == QLERROR_HOP)
        TestQQLinkFlag = TEST_FLAG_SWITCH_CHANNEL;
    else if (Ret == QLERROR_LOCK)
        TestQQLinkFlag = TEST_FLAG_LOCK_CHANNEL;        
}

VOID TestQQLink(uint8_t *szkey)
{
    SCAN_INFO_TABLE * pScanTable = NULL;
    UINT8 i, j;
	QQ_CONFIG_S qq_ConfigData;
	int err;
    
    DBGPRINT(DEBUG_TRACE, "Test QQLink start\n");   

    // scan all channel to get ap list
    pScanTable = OSMMalloc(sizeof(SCAN_INFO_TABLE) + sizeof(SCAN_INFO) * (32 -1));
    if (!pScanTable)
    {
        DBGPRINT(DEBUG_TRACE, "Test QQLink out of memory\n");
        return;
    }

    // init airkiss
     txd_qq_link_init(szkey);
 
SCAN_LOOP:
    TestQQLinkFlag = 0;
    InfSsidSet(0, 0);
    InfNetModeSet(PARAM_NET_MODE_STA_BSS);
    InfWiFiStart();
    pScanTable->InfoCount = 32;   
    InfScanStart(pScanTable, 0, 0);

    // wait scan done
    while (TestQQLinkFlag != TEST_FLAG_SCAN_DONE)
        OSTimeDly(10);
    InfWiFiStop();
    
    // sniff packets of every ap in the scan info list
    for (i = 0; i < pScanTable->InfoCount; i++)
    {
        //if (pScanTable->InfoList[i].Rssi < QQLINK_RSSI_MIN)
        //    continue;
    
        printf("InfSnifferStart\n");
        txd_qq_link_notify_hop(pScanTable->InfoList[i].Channel);
        InfSnifferStart(TestQQLinkRecvCb, pScanTable->InfoList[i].Bssid, pScanTable->InfoList[i].Channel);

        for (j = 0; j < QQLINK_LOCK_CH_TIMEOUT; j++)
        {
            // wait channel lock
            if (TestQQLinkFlag >= TEST_FLAG_LOCK_CHANNEL)
                break;
            OSTimeDly(1);
        }

        if (TestQQLinkFlag >= TEST_FLAG_LOCK_CHANNEL)
            break;
        InfWiFiStop();
    }

    if (TestQQLinkFlag >= TEST_FLAG_LOCK_CHANNEL)
    {
        for (j = 0; j < QQLINK_PROVISION_TIMEOUT; j++)// wait 60s
        {
            if (TestQQLinkFlag >= TEST_FLAG_QQLINK_DONE)
                break;
            OSTimeDly(1);
        }
    }
    else
        goto SCAN_LOOP;

    if (TestQQLinkFlag != TEST_FLAG_QQLINK_DONE)
    {
        InfWiFiStop();
        goto SCAN_LOOP;
    }

    DBGPRINT(DEBUG_TRACE, "QQLink ok\n");

	OSSemPend(pLinkUpSem, 0, &err); 

#if 0
    /* wait wifi link up */
    while (TestQQLinkFlag != TEST_FLAG_LINK_UP)
	{
		printf("******test*******\r\n");
        OSTimeDly(30);
	}
#endif
	
	if (TestQQLinkFlag != TEST_FLAG_LINK_UP)
    {
        InfWiFiStop();
        goto SCAN_LOOP;
    }

    OSMFree(pScanTable);
    txd_qq_link_destroy();

	qq_ConfigData.magicNumber = GAGENT_MAGIC_NUMBER;
	memcpy((unsigned char*)qq_ConfigData.wifi_ssid, (unsigned char*)SysParam.WiFiCfg.Ssid, 32);
    memcpy((unsigned char*)qq_ConfigData.wifi_key, (unsigned char*)SysParam.WiFiCfg.PSK, 32);
	nl6621_SaveConfigData(&qq_ConfigData);
    
    DBGPRINT(DEBUG_TRACE, "Test QQLink done\n");
}
